package com.hksj.vcm.service;

import cn.hutool.core.date.DateUtil;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.hksj.base.entity.Properties;
import com.hksj.base.query.DeviceOverviewQuery;
import com.hksj.base.service.DefaultDeviceService;
import com.hksj.base.vo.ChartVO;
import com.hksj.base.vo.DeviceVO;
import com.hksj.base.vo.LocationVO;
import com.hksj.common.core.common.SpecialityModelCodeEnum;
import com.hksj.common.core.exception.ApplicationException;
import com.hksj.common.core.util.EasyExcelUtil;
import com.hksj.vcm.constant.PropertyEnum;
import com.hksj.vcm.mapper.VavRoomMapper;
import com.hksj.vcm.query.*;
import com.hksj.vcm.vo.*;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.util.ObjectUtils;

import javax.servlet.http.HttpServletResponse;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.stream.Collectors;

@Service
public class VavRoomService {
    @Autowired
    private VavRoomMapper vavRoomMapper;
    @Autowired
    private DefaultDeviceService defaultDeviceService;

    public Page<VavRoomVO> pageRoomVav(VavRoomQuery query) {
        Page<VavRoomVO> page = new Page<>(query.getPageNum(), query.getPageSize());
        page.setRecords(new ArrayList<>());
        query.setSpecialityCode(SpecialityModelCodeEnum.vav_fj.getCode());
        List<VavRoomVO> roomList = vavRoomMapper.listRoom(query,query.getDisAblePage() ? null : page);
        if (!ObjectUtils.isEmpty(roomList)){
            List<Long> roomIdList = roomList.stream().map(VavRoomVO::getRoomId).collect(Collectors.toList());
            query.setRoomIdList(roomIdList);
            List<RoomDevicePropertyVO> devicePropertyList = vavRoomMapper.listRoomDeviceProperty(query);
            if (!ObjectUtils.isEmpty(devicePropertyList)){
                Map<Long, Map<String, String>> roomPropertyMap = devicePropertyList.stream().collect(Collectors.groupingBy(RoomDevicePropertyVO::getRoomId,
                        Collectors.toMap(RoomDevicePropertyVO::getProperty, RoomDevicePropertyVO::getValue)));
                for (VavRoomVO vavRoomVO : roomList) {
                    Map<String, String> propertyMap = roomPropertyMap.get(vavRoomVO.getRoomId());
                    if (!ObjectUtils.isEmpty(propertyMap)){
                        vavRoomVO.setSongfl(propertyMap.get(PropertyEnum.Songfl.getValue()));
                        vavRoomVO.setSongfkhd(propertyMap.get(PropertyEnum.Songfkhd.getValue()));
                        vavRoomVO.setPaifl(propertyMap.get(PropertyEnum.Paifl.getValue()));
                        vavRoomVO.setPaiffkhd(propertyMap.get(PropertyEnum.Paiffkhd.getValue()));
                        vavRoomVO.setKongqyl(propertyMap.get(PropertyEnum.Kongqyl.getValue()));
                    }
                }
            }
            defaultDeviceService.wrapAddr(roomList);
            page.setRecords(roomList);
        }
        return page;
    }

    public Page<RoomPropertyVO> pagePressureRecord(VavRecordQuery query){
        query.setPropertyList(Arrays.asList(PropertyEnum.Kongqyl.getValue()));
        query.setSpecialityCode(SpecialityModelCodeEnum.vav_fj.getCode());
        return pageReportRecord(query);
    }

    public Page<RoomPropertyVO> pageWindRecord(VavRecordQuery query) {
        query.setPropertyList(Arrays.asList(PropertyEnum.Paifl.getValue(),PropertyEnum.Songfl.getValue()));
        query.setSpecialityCode(SpecialityModelCodeEnum.vav_fj.getCode());
        return pageReportRecord(query);
    }


    public Page<RoomPropertyVO> pageReportRecord(VavRecordQuery query) {
        Page<RoomPropertyVO> page = new Page<>(query.getPageNum(), query.getPageSize());
        page.setRecords(new ArrayList<>());
        setQueryTime(query);
        List<DeviceVO> deviceList = vavRoomMapper.listDevice(query);
        if (!ObjectUtils.isEmpty(deviceList)){
            Map<String, List<String>> productDeviceIdListMap = deviceList.stream().collect(Collectors.groupingBy(DeviceVO::getProductId, Collectors.mapping(DeviceVO::getId, Collectors.toList())));
            List<VavRecordQuery> queryList = new ArrayList<>();
            for (String productId : productDeviceIdListMap.keySet()) {
                VavRecordQuery vavRecordQuery = new VavRecordQuery();
                BeanUtils.copyProperties(query,vavRecordQuery);
                vavRecordQuery.setTableName(defaultDeviceService.getTableName(productId));
                vavRecordQuery.setDeviceIdList(productDeviceIdListMap.get(productId));
                queryList.add(vavRecordQuery);
            }
            List<RoomPropertyVO> reportRecordList = vavRoomMapper.pageReportRecord(queryList, query);
            page.setRecords(reportRecordList);
            if (!query.getDisAblePage()){
                Long count = vavRoomMapper.reportRecordCount(queryList);
                page.setTotal(count);
            }
        }
        return page;
    }

    private void setQueryTime(VavTimeTypeQuery query){
        Date now = new Date();
        if (query.getType() == 1){
            query.setStartTime(DateUtil.offsetHour(now,-24).getTime());
            query.setEndTime(now.getTime());
        }else if(query.getType() == 2){
            query.setStartTime(DateUtil.offsetDay(now,-7).getTime());
            query.setEndTime(now.getTime());
        }else if(query.getType() == 3){
            query.setStartTime(DateUtil.beginOfDay(DateUtil.offsetDay(now,-29)).getTime());
            query.setEndTime(now.getTime());
        }else if(query.getType() == 4){
            query.setStartTime(DateUtil.beginOfDay(DateUtil.offsetMonth(now,-11)).getTime());
            query.setEndTime(now.getTime());
        }else{
            throw new ApplicationException("type 字段传值不正确");
        }
    }

    public List<ChartVO> listChartData(VavChartQuery query) {
        List<ChartVO> res = new ArrayList<>();
        VavRecordQuery vavRecordQuery = new VavRecordQuery();
        vavRecordQuery.setRoomId(query.getRoomId());
        vavRecordQuery.setType(query.getType());
        vavRecordQuery.setSpecialityCode(SpecialityModelCodeEnum.vav_fj.getCode());
        setQueryTime(vavRecordQuery);
        List<DeviceVO> deviceList = vavRoomMapper.listDevice(vavRecordQuery);

        List<Properties> list = new ArrayList<>();
        if (!ObjectUtils.isEmpty(deviceList)){
            Map<String, List<String>> productDeviceIdListMap = deviceList.stream().collect(Collectors.groupingBy(DeviceVO::getProductId, Collectors.mapping(DeviceVO::getId, Collectors.toList())));
            List<VavRecordQuery> queryList = new ArrayList<>();
            for (String productId : productDeviceIdListMap.keySet()) {
                VavRecordQuery tVavRecordQuery = new VavRecordQuery();
                BeanUtils.copyProperties(vavRecordQuery,tVavRecordQuery);
                tVavRecordQuery.setPropertyList(query.getPropertyList());
                tVavRecordQuery.setTableName(defaultDeviceService.getTableName(productId));
                tVavRecordQuery.setDeviceIdList(productDeviceIdListMap.get(productId));
                queryList.add(tVavRecordQuery);
            }
            list = vavRoomMapper.listRecord(queryList);
        }
        if (!ObjectUtils.isEmpty(list)){
            Map<String, List<Properties>> propertiesMap = list.stream().collect(Collectors.groupingBy(Properties::getProperty));
            for (String key : propertiesMap.keySet()) {
                res.add(new ChartVO(key,propertiesMap.get(key).get(0).getUnit(),propertiesMap.get(key)));
            }
        }
        return res;
    }

    public RoomOverviewVO getRoomOverview(DeviceOverviewQuery query) {
        return vavRoomMapper.getRoomOverview(query);
    }

    public List<VavRoomRankVO> listVavRoomRank(VavRoomRankQuery query) {
        if (query.getType() == 1){
            query.setProperty(PropertyEnum.Songfl.getValue());
        }else if(query.getType() == 2){
            query.setProperty(PropertyEnum.Paifl.getValue());
        }
        List<VavRoomRankVO> res = vavRoomMapper.listVavRoomRank(query);
        defaultDeviceService.wrapAddr(res);
        return res;
    }

    public List<VavDeviceRankVO> listVavDeviceRank(VavDeviceRankQuery query) {
        if (query.getType() == 1){
            query.setProperty(PropertyEnum.Songfl.getValue());
        }else if(query.getType() == 2){
            query.setProperty(PropertyEnum.Paifl.getValue());
        }
        List<VavDeviceRankVO> res = vavRoomMapper.listVavDeviceRank(query);
        defaultDeviceService.wrapAddr(res);
        return res;
    }

    public VavRoomVO getRoomCurrentProperty(Long roomId) {
        VavRoomQuery vavRoomQuery = new VavRoomQuery();
        vavRoomQuery.setRoomIdList(Arrays.asList(roomId));
        List<VavRoomVO> list =  this.pageRoomVav(vavRoomQuery).getRecords();
        if (!ObjectUtils.isEmpty(list)){
            return list.get(0);
        }
        return null;
    }

    public Page<RoomPropertyVO> pageDeviceRecord(VavDeviceRecordQuery query) {
        Page<RoomPropertyVO> page = new Page<>(query.getPageNum(), query.getPageSize());
        page.setRecords(new ArrayList<>());
        DeviceVO deviceInfo = defaultDeviceService.getDeviceInfo(query.getDeviceId());
        VavRecordQuery vavRecordQuery = new VavRecordQuery();
        vavRecordQuery.setPropertyList(Arrays.asList(PropertyEnum.Paifl.getValue(),PropertyEnum.Songfl.getValue()));
        vavRecordQuery.setSpecialityCode(SpecialityModelCodeEnum.vav_bfg.getCode());
        vavRecordQuery.setType(query.getType());
        setQueryTime(vavRecordQuery);
        vavRecordQuery.setTableName(defaultDeviceService.getTableName(deviceInfo.getProductId()));
        vavRecordQuery.setDeviceIdList(Arrays.asList(deviceInfo.getId()));

        List<RoomPropertyVO> reportRecordList = vavRoomMapper.pageReportRecord(Arrays.asList(vavRecordQuery), query);
        page.setRecords(reportRecordList);
        if (!query.getDisAblePage()){
            Long count = vavRoomMapper.reportRecordCount(Arrays.asList(vavRecordQuery));
            page.setTotal(count);
        }
        return page;
    }

    /**
     * 导出房间压力
     * @param query
     * @param response
     */
    public void exportPressureRecord(VavRecordQuery query, HttpServletResponse response) {
        query.setDisAblePage(true);
        List<RoomPropertyVO> records = pagePressureRecord(query).getRecords();
        List<ExportPressureVO> res = new ArrayList<>();
        if (!ObjectUtils.isEmpty(records)){
            for (int i = 0; i < records.size(); i++) {
                ExportPressureVO exportPressureVO = new ExportPressureVO();
                RoomPropertyVO roomPropertyVO = records.get(i);
                exportPressureVO.setSort(i + 1);
                exportPressureVO.setKongqyl(roomPropertyVO.getKongqyl());
                exportPressureVO.setCreateTime(DateUtil.formatDateTime(roomPropertyVO.getCreateTime()));
                res.add(exportPressureVO);
            }
        }

        LocationVO roomInfo = getRoomInfo(query.getRoomId());
        String fileName = new StringBuffer()
                .append(roomInfo.getFloorName())
                .append("_")
                .append(roomInfo.getRoomName())
                .append("_")
                .append("压力")
                .append(new SimpleDateFormat("_yyyyMMddHHmmss").format(new Date()))
                .toString();
        EasyExcelUtil.exportExcelData(response,fileName,res,ExportPressureVO.class);
    }

    /**
     * 导出房间送/排风
     * @param query
     * @param response
     */
    public void exportWindRecord(VavRecordQuery query, HttpServletResponse response) {
        query.setDisAblePage(true);
        List<RoomPropertyVO> records = pageWindRecord(query).getRecords();
        List<ExportWindVO> res = new ArrayList<>();
        if (!ObjectUtils.isEmpty(records)){
            for (int i = 0; i < records.size(); i++) {
                RoomPropertyVO roomPropertyVO = records.get(i);
                ExportWindVO exportWindVO = new ExportWindVO();
                exportWindVO.setSort(i + 1);
                exportWindVO.setSongfl(roomPropertyVO.getSongfl());
                exportWindVO.setPaifl(roomPropertyVO.getPaifl());
                exportWindVO.setCreateTime(DateUtil.formatDateTime(roomPropertyVO.getCreateTime()));
                res.add(exportWindVO);
            }
        }
        LocationVO roomInfo = getRoomInfo(query.getRoomId());
        String fileName = new StringBuffer()
                .append(roomInfo.getFloorName())
                .append("_")
                .append(roomInfo.getRoomName())
                .append("_")
                .append("送排风")
                .append(new SimpleDateFormat("_yyyyMMddHHmmss").format(new Date()))
                .toString();
        EasyExcelUtil.exportExcelData(response,fileName,res,ExportWindVO.class);
    }

    /**
     * 导出变风柜送/排风
     * @param query
     * @param response
     */
    public void exportDeviceRecord(VavDeviceRecordQuery query, HttpServletResponse response) {
        query.setDisAblePage(true);
        List<RoomPropertyVO> records = pageDeviceRecord(query).getRecords();
        List<ExportWindVO> res = new ArrayList<>();
        if (!ObjectUtils.isEmpty(records)){
            for (int i = 0; i < records.size(); i++) {
                RoomPropertyVO roomPropertyVO = records.get(i);
                ExportWindVO exportWindVO = new ExportWindVO();
                exportWindVO.setSort(i + 1);
                exportWindVO.setSongfl(roomPropertyVO.getSongfl());
                exportWindVO.setPaifl(roomPropertyVO.getPaifl());
                exportWindVO.setCreateTime(DateUtil.formatDateTime(roomPropertyVO.getCreateTime()));
                res.add(exportWindVO);
            }
        }
        DeviceVO deviceInfo = defaultDeviceService.getDeviceInfo(query.getDeviceId());
        defaultDeviceService.wrapAddr(Arrays.asList(deviceInfo));
        String fileName = new StringBuffer()
                .append(deviceInfo.getFloorName())
                .append("_")
                .append(deviceInfo.getRoomName())
                .append("_")
                .append(deviceInfo.getName())
                .append("_")
                .append("送排风")
                .append(new SimpleDateFormat("_yyyyMMddHHmmss").format(new Date()))
                .toString();
        EasyExcelUtil.exportExcelData(response,fileName,res,ExportWindVO.class);
    }

    public LocationVO getRoomInfo(String roomId){
        LocationVO room = vavRoomMapper.getRoomInfo(roomId);
        if (!ObjectUtils.isEmpty(room)){
            defaultDeviceService.wrapAddr(Arrays.asList(room));
        }
        return room;
    }
}
